import type { HookFetchPlugin, HookFetchRequestConfig } from 'hook-fetch';
import hookFetch from 'hook-fetch';
import { ElMessage } from 'element-plus';
import router from '@/routers';

// 定义响应接口
export interface IHttpResponse<T = any> {
  code: number;
  data: T;
  msg: string;
  success?: boolean;
}

export interface IObject<T = any> {
  [key: string]: T;
}

// 获取token的函数 - 需要根据项目实际情况调整
const getToken = (): string | null => {
  return localStorage.getItem('token') || sessionStorage.getItem('token');
};

// 获取语言设置 - 需要根据项目实际情况调整
const getLocaleLang = (): string => {
  return localStorage.getItem('locale') || 'zh-CN';
};

// 工具函数：通过键路径获取值
const getValueByKeys = (obj: any, path: string, defaultValue: any = undefined): any => {
  const keys = path.split('.');
  let result = obj;
  for (const key of keys) {
    if (result && typeof result === 'object' && key in result) {
      result = result[key];
    } else {
      return defaultValue;
    }
  }
  return result;
};

// 请求去重处理
const requestPending: IObject<number> = {};

const getRequestIdentify = (config: HookFetchRequestConfig): string => {
  const url = config.url || '';
  const params = new URLSearchParams(config.params as any).toString();
  return encodeURIComponent(url + (params ? '?' + params : ''));
};

// 登录重定向
const redirectLogin = (): void => {
  router.replace('/login');
};

// 请求拦截器插件
function requestInterceptorPlugin(): HookFetchPlugin<IHttpResponse> {
  return {
    name: 'requestInterceptor',
    beforeRequest: async (config) => {
      // 设置请求头
      config.headers = new Headers(config.headers);
      config.headers.set('X-Requested-With', 'XMLHttpRequest');
      config.headers.set('Request-Start', new Date().getTime().toString());
      config.headers.set('Accept-Language', getLocaleLang());

      // 设置token
      const token = getToken();
      if (token) {
        config.headers.set('token', token);
      }

      // GET请求添加时间戳防缓存
      if (config.method?.toUpperCase() === 'GET') {
        const url = new URL(config.url!, window.location.origin);
        url.searchParams.set('_t', new Date().getTime().toString());
        config.url = url.pathname + url.search;
      }

      // 处理表单数据
      if (config.headers.get('Content-Type')?.includes('application/x-www-form-urlencoded')) {
        if (config.body && typeof config.body === 'object') {
          const formData = new URLSearchParams();
          Object.entries(config.body as IObject).forEach(([key, value]) => {
            formData.append(key, String(value));
          });
          config.body = formData.toString();
        }
      }

      return config;
    },
  };
}

// 响应拦截器插件
function responseInterceptorPlugin(): HookFetchPlugin<IHttpResponse> {
  return {
    name: 'responseInterceptor',
    afterResponse: async (response) => {
      // 处理401未授权
      if (response.result?.code === 401) {
        redirectLogin();
        throw new Error('未授权，请登录');
      }

      return response;
    },
    onError: async (error) => {
      const status = getValueByKeys(error, 'response.status', 500);
      
      const httpCodeLabel: IObject<string> = {
        400: '请求参数错误',
        401: '未授权，请登录',
        403: '拒绝访问',
        404: `请求地址出错: ${getValueByKeys(error, 'response.url', '')}`,
        408: '请求超时',
        500: 'API接口报500错误',
        501: '服务未实现',
        502: '网关错误',
        503: '服务不可用',
        504: '网关超时',
        505: 'HTTP版本不受支持'
      };

      if (error && error.response) {
        console.error('请求错误', error.response);
      }

      if (status === 401) {
        redirectLogin();
      }

      const errorMessage = httpCodeLabel[status] || '接口错误';
      ElMessage.error(errorMessage);
      
      throw new Error(errorMessage);
    },
  };
}

// 请求去重插件
function requestDeduplicationPlugin(): HookFetchPlugin<IHttpResponse> {
  return {
    name: 'requestDeduplication',
    beforeRequest: async (config) => {
      const key = getRequestIdentify(config);
      
      if (requestPending[key]) {
        throw new Error('-999'); // 重复请求标识
      } else {
        requestPending[key] = 1;
      }

      return config;
    },
    afterResponse: async (response, config) => {
      const key = getRequestIdentify(config);
      delete requestPending[key];
      return response;
    },
    onError: async (error, config) => {
      if (config) {
        const key = getRequestIdentify(config);
        delete requestPending[key];
      }
      throw error;
    },
  };
}

// 创建hook-fetch实例
const hookFetchHttp = hookFetch.create<IHttpResponse>({
  baseURL: import.meta.env.VITE_API_URL || '',
  headers: {
    'Content-Type': 'application/json;charset=UTF-8',
  },
  plugins: [
    requestInterceptorPlugin(),
    responseInterceptorPlugin(),
    requestDeduplicationPlugin(),
  ],
});

// 导出默认的请求方法
export default (config: HookFetchRequestConfig): Promise<IHttpResponse> => {
  return hookFetchHttp.request(config).then(response => response.result!);
};

// 导出hook-fetch实例
export { hookFetchHttp };